package org.sql.statement.operation;

import org.sql.statement.builder.AbstractStatementBuilder;
import org.sql.statement.builder.Constants;
import org.sql.statement.builder.StatementBuilder;
import org.sql.statement.builder.StatementBuilder.StatementType;
import org.sql.statement.operation.intf.Operation;
import org.sql.statement.util.StatementUtil;

public class InsertOperation extends AbstractStatementBuilder implements
		Operation {

	private static final String STATEMENT_TYPE = StatementType.INSERT
			.toString();

	@Override
	public String buildStatement(StatementBuilder builder) {
		final StringBuilder sb = new StringBuilder();

		sb.append(STATEMENT_TYPE).append(CHAR_SPACE);
		sb.append(getIntoStatement(builder)).append(CHAR_SPACE);
		sb.append(getSetStatement(builder)).append(CHAR_SPACE);
		sb.append(getValuesStatement(builder));

		return sb.toString();
	}

	private StringBuilder getValuesStatement(StatementBuilder builder) {
		return new StringBuilder("VALUES").append(Constants.CHAR_SPACE)
				.append("(").append(getInsertValues(builder)).append(")");
	}

	private StringBuilder getSetStatement(StatementBuilder builder) {
		return new StringBuilder("SET").append(CHAR_SPACE).append("(")
				.append(getInsertKeys(builder)).append(")");
	}

	private StringBuilder getIntoStatement(StatementBuilder builder) {
		return new StringBuilder("INTO").append(CHAR_SPACE).append(
				buildFragment(builder.getTables()));
	}

	private String getInsertKeys(StatementBuilder builder) {
		return buildFragment(StatementUtil.getMapKeys(builder
				.getInsertArguments()));
	}

	private String getInsertValues(StatementBuilder builder) {
		return buildMarksFragment(builder.getInsertArguments().size());
	}
}
